/**
 * 测试信号量在线程之间的使用
 * 信号量也可以用于进程之间的同步；
 * @author: sundx
 * @date: 2020-05-27 23:00:47
 * @Last Modified by: sundx
 * @Last Modified time: 2020-06-01 19:25:27
 */

#include <pthread.h>
#include <semaphore.h>
#include <stack>
#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>

sem_t left, used; //剩余，可用；
std::stack<int> space;

void *consumer(void *);
void *producer(void *);

int main() {
  pthread_t consumerTid, producerTid;

  sem_init(&left, PTHREAD_PROCESS_PRIVATE, 5); // 剩余5个格子
  sem_init(&used, PTHREAD_PROCESS_PRIVATE, 0); // 有0个格子可被使用

  pthread_create(&consumerTid, nullptr, consumer, nullptr);
  pthread_create(&producerTid, nullptr, producer, nullptr);

  pthread_join(producerTid, nullptr);
  pthread_join(consumerTid, nullptr);
  sem_destroy(&left);
  sem_destroy(&used);

  pthread_exit(nullptr);
  return 0;
}
void *consumer(void *argv) { // 消费者
  while (1) {
    sem_wait(&used); //如果有格子可以被使用
    printf("consumer: %d\n", space.top());
    space.pop();
    sem_post(&left);
    sleep(rand() % 1);
  }
  return nullptr;
}
void *producer(void *argv) { // 生产者
  while (1) {
    sem_wait(&left);
    int i = rand() % 100;
    space.push(i);
    printf("producer: %d\n", space.top());
    sem_post(&used);
    sleep(rand() % 2);
  }
  return nullptr;
}